package com.vaha.presentation.rest;

import com.cyber.application.controller.AuthingTokenController;
import com.cyber.domain.constant.HttpResultCode;
import com.cyber.domain.entity.DataResponse;
import com.cyber.domain.entity.IdRequest;
import com.cyber.domain.entity.PagingData;
import com.cyber.domain.entity.Response;
import com.vaha.application.service.CategoryItemService;
import com.vaha.application.service.CategoryService;
import com.vaha.domain.entity.Category;
import com.vaha.domain.entity.CategoryItem;
import com.vaha.domain.entity.Order;
import com.vaha.domain.entity.Product;
import com.vaha.domain.request.*;
import lombok.RequiredArgsConstructor;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.*;

import javax.validation.Valid;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.stream.Collectors;

@RestController
@RequiredArgsConstructor
public class CategoryRest extends AuthingTokenController {

    private final CategoryService categoryService;

    private final CategoryItemService categoryItemService;


    @GetMapping("/user/category")
    public Response selectOneUserCategory(@Valid IdRequest request) {
        DataResponse<Category> response = new DataResponse<>();

        Category category = new Category();
        category.setId(request.getId());
        category.setTenantCode(getTenantCode());

        category = categoryService.selectOne(category);

        if (Objects.isNull(category)) {
            return response;
        }
        CategoryItem categoryItem = new CategoryItem();
        categoryItem.setLimit(Integer.MAX_VALUE);
        categoryItem.setCategoryCode(category.getCode());
        categoryItem.setSortBy("order_num");

        List<CategoryItem> categoryItems = categoryItemService.selectByIndex(categoryItem);

        category.setItems(categoryItems);
        response.setData(category);
        return response;
    }


    @GetMapping("/user/category/search")
    public Response searchUserCategory(@Valid CategoryRequest request) {
        DataResponse<PagingData<Category>> response = new DataResponse<>();
        Category category = request.toEvent(getTenantCode());
        PagingData<Category> categoryPage = categoryService.selectPage(category);

        if (!CollectionUtils.isEmpty(categoryPage.getData())) {
            List<String> categoryCodes = categoryPage.getData().stream().map(Category::getCode).collect(Collectors.toList());
            List<CategoryItem> productList = categoryItemService.selectByCodes(categoryCodes);

            if (!CollectionUtils.isEmpty(productList)) {

                Map<String, List<CategoryItem>> categoryItems = productList.stream().collect(Collectors.groupingBy(CategoryItem::getCategoryCode));

                for (Category categoryOne : categoryPage.getData()) {
                    List<CategoryItem> categoryItem = categoryItems.getOrDefault(categoryOne.getCode(), null);
                    categoryOne.setItems(categoryItem);
                }
            }
        }
        response.setData(categoryPage);
        return response;
    }


    @GetMapping("/admin/category/search")
    public Response searchCategory(@Valid CategoryRequest request) {
        DataResponse<PagingData<Category>> response = new DataResponse<>();
        Category category = request.toEvent(getTenantCode());
        PagingData<Category> categoryPage = categoryService.selectPage(category);
        response.setData(categoryPage);
        return response;
    }


    @GetMapping("/admin/category")
    public Response selectOneCategory(@Valid IdRequest request) {
        DataResponse<Category> response = new DataResponse<>();

        Category category = new Category();
        category.setId(request.getId());
        category.setTenantCode(getTenantCode());

        category = categoryService.selectOne(category);
        response.setData(category);
        return response;
    }

    @PostMapping("/admin/category")
    public Response saveCategory(@RequestBody @Valid CreateCategoryRequest request) {
        Category category = request.toEvent(getSessionId(), getTenantCode());
        int result = categoryService.save(category);
        if (result < 1) {
            return Response.fail(HttpResultCode.SERVER_ERROR);
        }
        return Response.success();
    }

    @PutMapping("/admin/category")
    public Response updateCategory(@RequestBody @Valid UpdateCategoryRequest request) {
        Category category = request.toEvent(getSessionId(), getTenantCode());
        int result = categoryService.updateById(category);
        if (result < 1) {
            return Response.fail(HttpResultCode.SERVER_ERROR);
        }
        return Response.success();
    }

    @DeleteMapping("/admin/category")
    public Response deleteCategory(@Valid IdRequest idRequest) {
        Category category = new Category();
        category.setId(idRequest.getId());

        category.setTenantCode(getTenantCode());
        category.setUpdator(getSessionId());
        category.setUpdateTime(new Date());

        int result = categoryService.deleteById(category);
        if (result < 1) {
            return Response.fail(HttpResultCode.SERVER_ERROR);
        }
        return Response.success();
    }


    @GetMapping("/admin/categoryitem/search")
    public Response searchCategoryItem(@Valid CategoryItemRequest request) {
        DataResponse<PagingData<CategoryItem>> response = new DataResponse<>();
        CategoryItem categoryitem = request.toEvent(getTenantCode());
        PagingData<CategoryItem> categoryItemPage = categoryItemService.selectPage(categoryitem);
        response.setData(categoryItemPage);
        return response;
    }


    @GetMapping("/admin/categoryitem")
    public Response selectOneCategoryItem(@Valid IdRequest idRequest) {
        DataResponse<CategoryItem> response = new DataResponse<>();

        CategoryItem categoryItem = new CategoryItem();
        categoryItem.setId(idRequest.getId());
        categoryItem.setTenantCode(getTenantCode());
        categoryItem = categoryItemService.selectOne(categoryItem);

        response.setData(categoryItem);
        return response;
    }

    @PostMapping("/admin/categoryitem")
    public Response saveCategoryItem(@RequestBody @Valid CreateCategoryItemRequest request) {
        CategoryItem categoryitem = request.toEvent(getSessionId(), getTenantCode());

        int result = categoryItemService.save(categoryitem);
        if (result < 1) {
            return Response.fail(HttpResultCode.SERVER_ERROR);
        }
        return Response.success();
    }

    @PutMapping("/admin/categoryitem")
    public Response updateCategoryItem(@RequestBody @Valid UpdateCategoryItemRequest request) {
        CategoryItem categoryitem = request.toEvent(getSessionId(), getTenantCode());
        int result = categoryItemService.updateById(categoryitem);
        if (result < 1) {
            return Response.fail(HttpResultCode.SERVER_ERROR);
        }
        return Response.success();
    }

    @DeleteMapping("/admin/categoryitem")
    public Response deleteCategoryItem(@Valid IdRequest idRequest) {
        CategoryItem categoryItem = new CategoryItem();
        categoryItem.setId(idRequest.getId());

        categoryItem.setTenantCode(getTenantCode());
        categoryItem.setUpdator(getSessionId());
        categoryItem.setUpdateTime(new Date());

        int result = categoryItemService.deleteById(categoryItem);
        if (result < 1) {
            return Response.fail(HttpResultCode.SERVER_ERROR);
        }
        return Response.success();
    }
}
